package com.dfbz.dao.base;

import com.dfbz.annotation.MyField;
import com.dfbz.annotation.MyTable;
import com.dfbz.utils.JDBCUtil;
import org.apache.commons.dbutils.BasicRowProcessor;
import org.apache.commons.dbutils.GenerousBeanProcessor;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.apache.commons.dbutils.handlers.ScalarHandler;

import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;

public class BaseDao<T> {
    private final String tableName;
    private final String keyName;
    private final Class<T> aClass;

    public BaseDao(Class<T> aClass){
        this.aClass=aClass;
        MyTable annotation = aClass.getDeclaredAnnotation(MyTable.class);
        if (null!=annotation){
            tableName=annotation.value();
            keyName=annotation.key();
        }else {
            tableName="default";
            keyName="id";
        }
    }

    //查找对应字段名的数据
    public List<T> findByCol(String key, String value) {
        List<T> list = new ArrayList<>();
        if (tableName!=null) {
            String sql = "select * from "+tableName+" where " + key + " = ?;";
            QueryRunner qr = new QueryRunner(JDBCUtil.getDataSource());
            try {
                list = qr.query(sql, new BeanListHandler<>(aClass,new BasicRowProcessor(new GenerousBeanProcessor())), value);
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
        return list;
    }
    //查找符合对应列名的数据
    public List<T> findByCols(String condition, Map<String,Object> map){
        List<T> list = new ArrayList<>();
        if (tableName!=null) {
            StringBuilder sb = new StringBuilder();
            sb.append("select * from ").append(tableName).append(" where ");
            if (null == map || map.isEmpty()) {
                sb.delete(sb.lastIndexOf("where"), sb.length());//查询全部
            } else {
                Set<String> keySet = map.keySet();
                for (String key : keySet) {
                    sb.append(key).append("='").append(map.get(key)).append("' ").append(condition).append(" ");
                }
                sb.delete(sb.lastIndexOf(condition), sb.length());
            }
            QueryRunner qr = new QueryRunner(JDBCUtil.getDataSource());
            try {
                list = qr.query(sb.toString(), new BeanListHandler<>(aClass,new BasicRowProcessor(new GenerousBeanProcessor())));
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
        return list;
    }
    //插入数据
    public int save(Object obj){
        StringBuilder sql = new StringBuilder();
        sql.append("insert into ").append(tableName).append(" values(");
        Class<?> aClass = obj.getClass();
        Field[] fields = aClass.getDeclaredFields();
        for (int i = 0; i < fields.length; i++) {
            if (i==fields.length-1){
                sql.append("?)");
            }else {
                sql.append("?,");
            }
        }
        QueryRunner qr = new QueryRunner(JDBCUtil.getDataSource());
        int row = 0;
        try {
            Object[] params = new Object[fields.length];
            for (int i = 0; i < fields.length; i++){
                String name = fields[i].getName();
                String methodName = "get" + name.substring(0, 1).toUpperCase() + name.substring(1);
                Method method = aClass.getDeclaredMethod(methodName);
                Object value = method.invoke(obj);
                params[i]=value;
            }
            row = qr.update(sql.toString(),params);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return row;
    }
    //更新数据
    public int update(Object obj) {
        int row = 0;
        StringBuilder sql = new StringBuilder();
        sql.append("update ").append(tableName).append(" set ");

        Class<?> aClass = obj.getClass();
        Field[] fields = aClass.getDeclaredFields();
        for (Field field:fields) {
            String columnName = field.getName();
            MyField annotation = field.getAnnotation(MyField.class);
            if (null!=annotation){
                columnName = annotation.value();
            }
            sql.append(columnName).append("=?,");
        }
        sql.delete(sql.lastIndexOf(","),sql.length());
        sql.append(" where ").append(keyName).append(" = ?");

        QueryRunner qr = new QueryRunner(JDBCUtil.getDataSource());
        try {
            Object[] params = new Object[fields.length+1];
            Object id=null;
            for (int i = 0; i < fields.length; i++){
                String fieldName = fields[i].getName();
                String columnName = fields[i].getName();
                MyField annotation = fields[i].getAnnotation(MyField.class);
                if (null!=annotation){
                    columnName = annotation.value();
                }
                String methodName = "get" + fieldName.substring(0, 1).toUpperCase() + fieldName.substring(1);
                Method method = aClass.getDeclaredMethod(methodName);
                Object value = method.invoke(obj);
                if (columnName.equalsIgnoreCase(keyName)){
                    id=value;
                }
                params[i]=value;
            }
            params[fields.length]=id;
            row = qr.update(sql.toString(),params);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return row;
    }
    //查找数据
    public T findById(Object id){
        T obj = null;
        String sql = "select * from "+tableName+" where "+keyName+" = ?";
        QueryRunner qr = new QueryRunner(JDBCUtil.getDataSource());
        try {
            obj = qr.query(sql,new BeanHandler<>(aClass,new BasicRowProcessor(new GenerousBeanProcessor())),id);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return obj;
    }
    //删除数据
    public int deleteById(Object id){
        int row = 0;
        String sql = "delete from "+tableName+" where "+keyName+" =?";
        QueryRunner qr = new QueryRunner(JDBCUtil.getDataSource());
        try {
            row = qr.update(sql,id);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return row;
    }
}




